package cn.rkylin.oms.base.channel.service;

import java.security.MessageDigest;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Map;

import com.alibaba.fastjson.TypeReference;

import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Repository;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.github.pagehelper.PageInfo;

import cn.rkylin.apollo.common.util.HttpUtils;
import cn.rkylin.core.service.ApolloService;
import cn.rkylin.oms.base.channel.dao.IChannelDAO;
import cn.rkylin.oms.base.channel.domain.Channel;
import cn.rkylin.oms.base.channel.vo.ChannelVO;
import cn.rkylin.oms.base.channel.vo.MdmChannel;
import cn.rkylin.oms.base.channel.vo.MdmData;
import cn.rkylin.oms.base.channel.vo.MdmRecords;
import cn.rkylin.oms.base.channel.vo.MdmResult;

/**
 * 渠道Service
 */
@Repository(value = "channelService")
public class ChannelServiceImpl extends ApolloService implements IChannelService {

	@Autowired
	private IChannelDAO channelDAO;

	@Value("${mdm.server.security}")
	private String mdmServerSecurity;

	@Value("${mdm.server.url}")
	private String mdmServerUrl;

	@Value("${mdm.server.appId}")
	private String mdmServerAppId;

	/**
	 * 查询渠道列表
	 * 
	 * @param page
	 *            页号
	 * @param rows
	 *            页大小
	 * @param channelVO
	 *            渠道VO
	 * @return 渠道列表
	 * @throws Exception
	 *             异常
	 */
	@SuppressWarnings("rawtypes")
	public PageInfo findByWhere(int page, int rows, ChannelVO channelVO) throws Exception {
		PageInfo<ChannelVO> channelVOList = findPage(page, rows, "pageSelectChannel", channelVO);
		return channelVOList;
	}

	/**
	 * 下载渠道
	 * 
	 * @param page
	 *            页号
	 * @param rows
	 *            页大小
	 * @return 返回结果
	 * @throws Exception
	 *             异常
	 */
	public String downloadChannel(int page, int rows) throws Exception {

		// 得到渠道数据
		String data = "{\"system_code\":\"ERP001\",\"page\":" + page + ",\"page_size\":\"1000\"}";
		String t = String.valueOf((new Date()).getTime());
		String sign = MD5(mdmServerSecurity + t + data);

		StringBuffer sb = new StringBuffer();
		sb.append(mdmServerUrl + "/api/mdm_channel_template_instance/query" + "?");
		sb.append("appId=" + mdmServerAppId);
		sb.append("&timestamp=" + t);
		sb.append("&sign=" + sign);
		sb.append("&system_code=ERP001&page=" + page + "&page_size=1000");
//		sb.append("&data=" + data);

		String json = HttpUtils.sendByPost(sb.toString(),data);//HttpUtils.sendByGet(sb.toString(), null);
		JSONObject mdmChannelJson = JSON.parseObject(json);
		JSONObject mdmResultJson = mdmChannelJson.getJSONObject("result");
		JSONObject mdmDataJson = mdmResultJson.getJSONObject("data");
		JSONArray mdmRecodesJson = mdmDataJson.getJSONArray("records");

		List<MdmRecords> listRecodes = new ArrayList<MdmRecords>();
		listRecodes = JSON.parseArray(mdmRecodesJson.toJSONString(), MdmRecords.class);
		mdmDataJson.remove("records");
		MdmData mdmData = JSON.parseObject(mdmDataJson.toJSONString(), MdmData.class);
		mdmResultJson.remove("data");
		MdmResult mdmResult = JSON.parseObject(mdmResultJson.toJSONString(), MdmResult.class);
		mdmChannelJson.remove("result");
		MdmChannel mdmChannel = JSON.parseObject(mdmChannelJson.toJSONString(), MdmChannel.class);

		// S1:调用成功 S2:登录验证失败 S3:验签失败 S4:系统异常
		if (!"S1".equals(mdmChannel.getStatus())) {
			if ("S2".equals(mdmResult.getStatus())) {
				return "登录验证失败";
			} else if ("S3".equals(mdmResult.getStatus())) {
				return "验签失败";
			} else if ("S4".equals(mdmResult.getStatus())) {
				return "系统异常";
			}
		}

		// Y1：请求成功 Y2：参数错误 Y3：唯一性校验失败 Y4：数据状态异常
		if (!"Y1".equals(mdmResult.getStatus())) {
			if ("Y2".equals(mdmResult.getStatus())) {
				return "参数错误";
			} else if ("Y3".equals(mdmResult.getStatus())) {
				return "唯一性校验失败";
			} else if ("Y4".equals(mdmResult.getStatus())) {
				return "数据状态异常";
			}
		}

		for (int i = 0; i < listRecodes.size(); i++) {
			MdmRecords mdmRecords = listRecodes.get(i);
			Channel channel = new Channel();
			channel.setChannelId(java.util.UUID.randomUUID().toString().replace("-", ""));
			channel.setChannelCode(mdmRecords.getChannel_code());
			channel.setChannelName(mdmRecords.getChannel_name());
			channel.setEntId("51f17f6ddbae11e68c4d001e67c7ec3a");
			channel.setProjectCode(mdmRecords.getProject_code());
			channel.setProject(mdmRecords.getProject());
			channel.setMdmCode(mdmRecords.getMdm_code());
			channel.setRemark(mdmRecords.getRemark());

			int result = channelDAO.updateChannel(channel);
			if (result == 0) {
				channelDAO.insertChannel(channel);
			}
		}

		// 如果一页放不下，递归调用
		rows = rows + listRecodes.size();
		if (Integer.valueOf(mdmData.getTotalCount()) - rows > 0) {
			String msg = downloadChannel(Integer.valueOf(page) + 1, rows);
			if (!"".equals(msg)) {
				return msg;
			}
		}

		return "";
	}

	/**
	 * 下载渠道(最新的渠道下载)
	 *
	 * @param page
	 *            页号
	 * @param rows
	 *            页大小
	 * @return 返回结果
	 * @throws Exception
	 *             异常
	 */
	public String downloadChannelNew(int page, int rows) throws Exception {

		// 得到渠道数据
		String data = "{\"system_code\":\"ERP001\",\"page\":" + page + ",\"page_size\":\"1000\"}";
		String t = String.valueOf((new Date()).getTime());
		String sign = MD5(mdmServerSecurity + t + data);

		StringBuffer sb = new StringBuffer();
		sb.append(mdmServerUrl + "/api/mdm_channel_cloud_template_instance/query" + "?");
		sb.append("appId=" + mdmServerAppId);
		sb.append("&timestamp=" + t);
		sb.append("&sign=" + sign);
		sb.append("&system_code=ERP001&page=" + page + "&page_size=1000");
//		sb.append("&data=" + data);

		String json = HttpUtils.sendByPost(sb.toString(),data);//HttpUtils.sendByGet(sb.toString(), null);
		JSONObject mdmChannelJson = JSON.parseObject(json);
		JSONObject mdmResultJson = mdmChannelJson.getJSONObject("result");
		JSONObject mdmDataJson = mdmResultJson.getJSONObject("data");
		JSONArray mdmRecodesJson = mdmDataJson.getJSONArray("records");

		List<String> listRecodes = new ArrayList<String>();
		listRecodes = JSON.parseArray(mdmRecodesJson.toJSONString(), String.class);
		mdmDataJson.remove("records");
		MdmData mdmData = JSON.parseObject(mdmDataJson.toJSONString(), MdmData.class);
		mdmResultJson.remove("data");
		MdmResult mdmResult = JSON.parseObject(mdmResultJson.toJSONString(), MdmResult.class);
		mdmChannelJson.remove("result");
		MdmChannel mdmChannel = JSON.parseObject(mdmChannelJson.toJSONString(), MdmChannel.class);

		// S1:调用成功 S2:登录验证失败 S3:验签失败 S4:系统异常
		if (!"S1".equals(mdmChannel.getStatus())) {
			if ("S2".equals(mdmResult.getStatus())) {
				return "登录验证失败";
			} else if ("S3".equals(mdmResult.getStatus())) {
				return "验签失败";
			} else if ("S4".equals(mdmResult.getStatus())) {
				return "系统异常";
			}
		}

		// Y1：请求成功 Y2：参数错误 Y3：唯一性校验失败 Y4：数据状态异常
		if (!"Y1".equals(mdmResult.getStatus())) {
			if ("Y2".equals(mdmResult.getStatus())) {
				return "参数错误";
			} else if ("Y3".equals(mdmResult.getStatus())) {
				return "唯一性校验失败";
			} else if ("Y4".equals(mdmResult.getStatus())) {
				return "数据状态异常";
			}
		}

		for (int i = 0; i < listRecodes.size(); i++) {
			Map<String, Object> map = JSONObject.parseObject(listRecodes.get(i), new TypeReference<Map<String, Object>>() {
			});
			Channel channel = new Channel();
			channel.setChannelId(java.util.UUID.randomUUID().toString().replace("-", ""));
			channel.setChannelCode((String)map.get("channel_code"));
			channel.setChannelName((String)map.get("channel_name"));
			channel.setEntId("51f17f6ddbae11e68c4d001e67c7ec3a");
			channel.setProjectCode((String)map.get("project_code"));
			channel.setProject((String)map.get("project"));
			channel.setMdmCode((String)map.get("mdm_code"));
			channel.setRemark((String)map.get("remark"));
			channel.setChannelType((String)map.get("channel_type"));
			channel.setSalesPaltform((String)map.get("sales_paltform"));
			if ("y".equals((String)map.get("disabled_flag"))){
				channel.setEnable("n");
			} else {
				channel.setEnable("y");
			}
			channel.setMdmResponse(listRecodes.get(i));
			int result = channelDAO.updateChannel(channel);
			if (result == 0) {
				channelDAO.insertChannel(channel);
			}
		}

		// 如果一页放不下，递归调用
		rows = rows + listRecodes.size();
		if (Integer.valueOf(mdmData.getTotalCount()) - rows > 0) {
			String msg = downloadChannel(Integer.valueOf(page) + 1, rows);
			if (!"".equals(msg)) {
				return msg;
			}
		}

		return "";
	}

	/**
	 * 接受主动发过来的数据变更
	 * 
	 * @param json
	 *            JSON
	 * @param type
	 *            类型
	 * @throws Exception
	 *             异常
	 */
	public List<MdmRecords> receiveChannel(String json, String type) throws Exception {
		List<MdmRecords> listRecodes = new ArrayList<MdmRecords>();
		listRecodes = JSON.parseArray(json, MdmRecords.class);

		for (int i = 0; i < listRecodes.size(); i++) {
			MdmRecords mdmRecords = listRecodes.get(i);
			Channel channel = new Channel();
			channel.setChannelId(java.util.UUID.randomUUID().toString().replace("-", ""));
			channel.setChannelCode(mdmRecords.getChannel_code());
			channel.setChannelName(mdmRecords.getChannel_name());
			channel.setEntId("51f17f6ddbae11e68c4d001e67c7ec3a");
			channel.setProjectCode(mdmRecords.getProject_code());
			channel.setProject(mdmRecords.getProject());
			channel.setMdmCode(mdmRecords.getMdm_code());
			channel.setRemark(mdmRecords.getRemark());
			//暂时不要对应删除
//			if ("3".equals(type)) {
//				channel.setDeleted("y");
//			} else {
//				channel.setDeleted("n");
//			}

			int result = channelDAO.updateChannel(channel);
			if (result == 0) {
				channelDAO.insertChannel(channel);
			}
		}
		return listRecodes;
	}

	/**
	 * 接受主动发过来的数据变更
	 *
	 * @param json
	 *            JSON
	 * @param type
	 *            类型
	 * @throws Exception
	 *             异常
	 */
	public List<String> receiveChannelNew(String json, String type) throws Exception {
		List<String> listRecodes = new ArrayList<String>();
		listRecodes = JSON.parseArray(json, String.class);

		for (int i = 0; i < listRecodes.size(); i++) {
			Map<String, Object> map = JSONObject.parseObject(listRecodes.get(i), new TypeReference<Map<String, Object>>() {
			});
			Channel channel = new Channel();
			channel.setChannelId(java.util.UUID.randomUUID().toString().replace("-", ""));
			channel.setChannelCode((String)map.get("channel_code"));
			channel.setChannelName((String)map.get("channel_name"));
			channel.setEntId("51f17f6ddbae11e68c4d001e67c7ec3a");
			channel.setProjectCode((String)map.get("project_code"));
			channel.setProject((String)map.get("project"));
			channel.setMdmCode((String)map.get("mdm_code"));
			channel.setRemark((String)map.get("remark"));
			channel.setChannelType((String)map.get("channel_type"));
			channel.setSalesPaltform((String)map.get("sales_paltform"));
			if ("y".equals((String)map.get("disabled_flag"))){
				channel.setEnable("n");
			} else {
				channel.setEnable("y");
			}
			channel.setMdmResponse(listRecodes.get(i));
			//暂时不要对应删除
//			if ("3".equals(type)) {
//				channel.setDeleted("y");
//			} else {
//				channel.setDeleted("n");
//			}

			int result = channelDAO.updateChannel(channel);
			if (result == 0) {
				channelDAO.insertChannel(channel);
			}
		}
		return listRecodes;
	}

	/**
	 * MD5字符串
	 * 
	 * @param message
	 *            字符串
	 * @return MD5后的字符串
	 */
	private static String MD5(String message) {
		String mess = message;
		char hexDigits[] = { '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F' };
		try {
			byte[] btInput = mess.getBytes("UTF-8");
			// 获得MD5摘要算法的 MessageDigest 对象
			MessageDigest mdInst = MessageDigest.getInstance("MD5");
			// 使用指定的字节更新摘要
			mdInst.update(btInput);
			// 获得密文
			byte[] md = mdInst.digest();
			// 把密文转换成十六进制的字符串形式
			int j = md.length;
			char str[] = new char[j * 2];
			int k = 0;
			for (int i = 0; i < j; i++) {
				byte byte0 = md[i];
				str[k++] = hexDigits[byte0 >>> 4 & 0xf];
				str[k++] = hexDigits[byte0 & 0xf];
			}
			return new String(str);
		} catch (Exception e) {
			e.printStackTrace();
			return null;
		}
	}

	/**
	 * 删除
	 */
	@Override
	public int delete(String channelID) throws Exception {
		return channelDAO.deleteChannel(channelID);
	}
    
	/**
     * 创建渠道信息
     * @param channelVO
     * @return
     * @throws Exception
     */
	@Override
	public Channel insert(ChannelVO channelVO) throws Exception {
		
		    Channel channel = new Channel();
	        BeanUtils.copyProperties(channelVO, channel);
	        channelDAO.insertChannel(channel);
	        return channel;
	}

	/**
	 * 通过id获取渠道
	 */
	@Override
	public ChannelVO getChannelById(String id) throws Exception {
		ChannelVO channelVO = channelDAO.findById(id);
        return channelVO;
		
	}
     
	/**
	 * 获取code
	 */
	@Override
	public ChannelVO getChannelByChannelCode(ChannelVO channelVO) throws Exception {
		
		return channelDAO.selectByChannelCode(channelVO);
	}
    
	/**
	 * 修改渠道
	 */
	@Override
	public Channel update(ChannelVO channelVO) throws Exception {
		Channel channel = new Channel();
        BeanUtils.copyProperties(channelVO, channel);
        channelDAO.updateChannel(channel);
        return channel;
	}

}
